using System;
using System.Collections.Generic;
using System.Text;
using System.Threading;
using FreeLancer.HRB.Services;
using FreeLancer.HRB.Domains;

namespace FreeLancer.HRB.Core
{
  public class Event : IPublishable
  {
    #region Properties

    private FreeLancer.HRB.Domains.Events _data;
    /// <summary>
    /// Data of Page.
    /// </summary>
    public FreeLancer.HRB.Domains.Events Data
    {
      get { return _data; }
      set { _data = value; }
    }

    /// <summary>
    /// Gets or sets the Slug of the Page.
    /// A Slug is the relative URL used by the pages.
    /// </summary>
    public string Slug
    {
      get
      {
        return Utils.RemoveIllegalCharacters(Title);
      }
    }

    private static object _syncRoot = new object();
    private static List<Event> _events;
    /// <summary>
    /// A sorted collection of all posts in the blog.
    /// Sorted by date.
    /// </summary>
    public static List<Event> Events
    {
      get
      {
        if (_events == null)
        {
          lock (_syncRoot)
          {
            if (_events == null)
            {
              _events = FillEvents();
              _events.TrimExcess();
              _events.Sort(delegate(Event p1, Event p2)
              { return String.Compare(p1.Title, p2.Title); });
            }
          }
        }

        return _events;
      }
    }

    private Guid _event;

    /// <summary>
    /// Parent page
    /// </summary>
    public Guid Parent
    {
      get { return _event; }
      set { _event = value; }
    }

    #endregion

    #region IPublishable Members

    public string Title
    {
      get { return _data.Title; }
    }

    public string Content
    {
      get { return _data.Description; }
    }

    public DateTime DateCreated
    {
      get { return _data.DateCreated; }
    }

    public DateTime DateModified
    {
      get { return _data.DateModified; }
    }

    public Guid Id
    {
      get { return _data.EventId; }
    }

    public string RelativeLink
    {
      get
      {
        string slug = Utils.RemoveIllegalCharacters(Slug) + WebAppSettings.Instance.FileExtension;
        return Utils.RelativeWebRoot + "event/" + slug;
      }
    }

    public Uri AbsoluteLink
    {
      get { return Utils.ConvertToAbsolute(RelativeLink); }
    }

    public string Description
    {
      get { return _data.Description; }
    }

    public string Author
    {
      get { return string.Empty; }
    }

    public void OnServing(ServingEventArgs eventArgs)
    {
      if (Serving != null)
      {
        Serving(this, eventArgs);
      }
    }

    public List<Category> Categories
    {
      get { return null; }
    }

    public bool IsPublished
    {
      get { return _data.IsPublished; }
    }

    public bool IsVisible
    {
      get { return Thread.CurrentPrincipal.Identity.IsAuthenticated && _data.IsPublished; }
    }

    #endregion

    #region Constructor

    /// <summary>
    /// Construtor
    /// </summary>
    /// <param name="data">Event data</param>
    public Event(FreeLancer.HRB.Domains.Events data)
    {
      if (data == null)
        throw new ArgumentNullException();

      _data = data;
      Initialize();
    }

    private void Initialize()
    {
      EventsService service = GlobalCache.EventsService;
      FreeLancer.HRB.Domains.Events eventDomain = service.GetByEventIdLanguageId(_data.EventId, _data.LanguageId);

      if (_event != null)
        _event = eventDomain.EventId;
    }

    #endregion

    #region Events

    /// <summary>
    /// Occurs when the page is being served to the output stream.
    /// </summary>
    public static event EventHandler<ServingEventArgs> Serving;
    /// <summary>
    /// Raises the event in a safe way
    /// </summary>
    public static void OnServing(Page page, ServingEventArgs arg)
    {
      if (Serving != null)
      {
        Serving(page, arg);
      }
    }

    #endregion

    #region Helpers

    private static List<Event> FillEvents()
    {
      List<Event> events = new List<Event>();
      EventsService service = GlobalCache.EventsService;

      TList<FreeLancer.HRB.Domains.Events> eventDomains = service.GetAll();
      foreach (FreeLancer.HRB.Domains.Events eventDomain in eventDomains)
      {
        events.Add(new Event(eventDomain));
      }

      return events;
    }

    #endregion
  }
}
